package com.whfc.quality.service.impl;

import com.whfc.common.exception.BizException;
import com.whfc.common.result.ResultEnum;
import com.whfc.common.util.RegexUtil;
import com.whfc.quality.dao.QualityPartMapper;
import com.whfc.quality.dto.QualityPartDTO;
import com.whfc.quality.dto.QualityPartImportDTO;
import com.whfc.quality.dto.QualityPartImportResultDTO;
import com.whfc.quality.entity.QualityPart;
import com.whfc.quality.param.QualityPartAddParam;
import com.whfc.quality.param.QualityPartEditParam;
import com.whfc.quality.service.QualityPartService;
import org.apache.dubbo.config.annotation.DubboService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;

import java.util.ArrayList;
import java.util.List;

/**
 * @author : qzexing
 * @version : 1.0
 * @date : 2020-07-30 16:26
 */
@DubboService(interfaceClass = QualityPartService.class, version = "1.0.0", timeout = 5000)
public class QualityPartServiceImpl implements QualityPartService {

    private Logger logger = LoggerFactory.getLogger(this.getClass());

    @Autowired
    private QualityPartMapper qualityPartMapper;

    @Override
    public List<QualityPartDTO> list(Integer deptId, String keyword) throws BizException {
        List<QualityPartDTO> list = qualityPartMapper.selectQualityPartDTOList(deptId, keyword);
        return parseTree(list);
    }

    @Override
    public void add(QualityPartAddParam addParam) throws BizException {
        Integer pid = addParam.getPid();
        QualityPart part = new QualityPart();
        String code = addParam.getCode();
        if (!RegexUtil.isInteger(code)) {
            throw new BizException(ResultEnum.FAILURE.getCode(), "编码格式错误.");
        }
        if (pid != null) {
            QualityPart qualityPart = qualityPartMapper.selectByPrimaryKey(pid);
            if (qualityPart == null) {
                throw new BizException(ResultEnum.FAILURE.getCode(), "父检测部位不存在.");
            }
            code = qualityPart.getCode() + "." + code;
            part.setPid(qualityPart.getId());
        } else {
            part.setPid(0);
        }
        QualityPart qualityPart = qualityPartMapper.selectPartByCode(code, addParam.getDeptId());
        if (qualityPart != null) {
            throw new BizException(ResultEnum.FAILURE.getCode(), "该编码已存在.");
        }
        part.setCode(code);
        part.setDeptId(addParam.getDeptId());
        part.setName(addParam.getName());
        qualityPartMapper.insertSelective(part);
    }

    @Override
    public void edit(QualityPartEditParam editParam) throws BizException {
        String code = editParam.getCode();
        if (!RegexUtil.isInteger(code)) {
            throw new BizException(ResultEnum.FAILURE.getCode(), "编码格式错误.");
        }
        QualityPart qualityPart = qualityPartMapper.selectByPrimaryKey(editParam.getPartId());
        if (qualityPart == null) {
            throw new BizException(ResultEnum.FAILURE.getCode(), "该检测部位不存在.");
        }
        QualityPart prentPart = qualityPartMapper.selectByPrimaryKey(qualityPart.getPid());

        if (prentPart != null) {
            code = prentPart.getCode() + "." + code;
        }
        QualityPart part = qualityPartMapper.selectPartByCode(code, qualityPart.getDeptId());
        if (part != null && !qualityPart.getCode().equals(code)) {
            throw new BizException(ResultEnum.FAILURE.getCode(), "该编码已存在.");
        }
        Integer length = qualityPart.getCode().length();
        List<QualityPart> parts = qualityPartMapper.selectLikeCode(qualityPart.getCode() + ".");
        for (QualityPart lowPart : parts) {
            lowPart.setCode(code + lowPart.getCode().substring(length));
            qualityPartMapper.updateByPrimaryKeySelective(lowPart);
        }

        qualityPartMapper.updateNameById(editParam.getPartId(), code, editParam.getName());
    }


    @Override
    public void del(Integer partId) throws BizException {
        if (!qualityPartMapper.selectByPid(partId).isEmpty()) {
            throw new BizException(ResultEnum.FAILURE.getCode(), "有子节点存在无法删除.");
        }
        qualityPartMapper.logicDel(partId);
    }

    @Override
    public QualityPartImportResultDTO importPart(Integer deptId, List<QualityPartImportDTO> list) throws BizException {
        try {
            //取出所有的编码
            List<String> codeList = qualityPartMapper.selectCodeList(deptId);
            //数据处理
            int successNumber = 0;
            int failedNumber = 0;
            for (QualityPartImportDTO importParam : list) {
                String code = importParam.getCode();
                if (code == null) {
                    importParam.setResult("编码错误");
                    failedNumber += 1;
                    continue;
                }
                if (codeList.contains(code)) {
                    importParam.setResult("编码已存在.");
                    failedNumber += 1;
                    continue;
                }
                QualityPart part = new QualityPart();
                part.setDeptId(deptId);
                part.setCode(code);
                part.setName(importParam.getName());
                if (code.contains(".")) {
                    String parentCode = code.substring(0, code.lastIndexOf("."));
                    if (!codeList.contains(parentCode)) {
                        importParam.setResult("父节点编码不存在.");
                        failedNumber += 1;
                        continue;
                    }
                    QualityPart parentPart = qualityPartMapper.selectPartByCode(parentCode, deptId);
                    part.setPid(parentPart.getId());
                } else {
                    part.setPid(0);
                }
                qualityPartMapper.insertSelective(part);
                codeList.add(code);
                successNumber += 1;
            }
            QualityPartImportResultDTO resultDTO = new QualityPartImportResultDTO();
            resultDTO.setSuccessNumber(successNumber);
            resultDTO.setFailNumber(failedNumber);
            resultDTO.setImportResultList(list);
            return resultDTO;
        } catch (Exception e) {
            logger.error("导入模板失败", e.getMessage());
            throw new BizException(ResultEnum.FAILURE.getCode(), "导入模板失败.");
        }
    }

    /**
     * 树形处理数据
     *
     * @param list 部位列表
     * @return 部位列表
     */
    private List<QualityPartDTO> parseTree(List<QualityPartDTO> list) {
        List<QualityPartDTO> result = new ArrayList<>();

        // 1、获取第一级节点
        for (QualityPartDTO qualityPartDTO : list) {
            if (0 == qualityPartDTO.getPid()) {
                result.add(qualityPartDTO);
            }
        }

        // 2、递归获取子节点
        for (QualityPartDTO qualityPartDTO : result) {
            recursiveTree(qualityPartDTO, list);
        }

        return result;
    }

    /**
     * 递归获取子节点
     *
     * @param parent 父节点
     * @param list   部位列表
     */
    private void recursiveTree(QualityPartDTO parent, List<QualityPartDTO> list) {
        for (QualityPartDTO qualityPartDTO : list) {
            if (parent.getPartId().equals(qualityPartDTO.getPid())) {
                recursiveTree(qualityPartDTO, list);
                List<QualityPartDTO> children = parent.getChildren();
                if (children == null) {
                    children = new ArrayList<>();
                    parent.setChildren(children);
                }
                children.add(qualityPartDTO);
            }
        }
    }

}